package com.sanchunhui.psc.utils

import android.app.Service
import android.content.Context
import android.content.Intent
import android.content.IntentFilter
import android.net.ConnectivityManager
import android.util.Log
import org.eclipse.paho.android.service.MqttAndroidClient
import org.eclipse.paho.client.mqttv3.*
import org.json.JSONObject

/**
 * @Author zyx
 * @Date 2021/5/26-17:29
 * @Dscribe
 */
abstract class MQTTService : Service(){

    private lateinit var mqttClient: MqttAndroidClient
    private lateinit var userName : String // 用户名
    private lateinit var passWord: String // 密码
    private lateinit var myReceiver: MyReceiver

    companion object {
        const val TAG = "AndroidMqttClient"
    }

    override fun onCreate() {
        super.onCreate()
    }

    override fun onStartCommand(intent: Intent?, flags: Int, startId: Int): Int {
        userName = "pscemqx"
        passWord = "123456"
        connect(this)
        return super.onStartCommand(intent, flags, startId)
    }

    /*
   * 连接 MQTT 服务器
   * */
    fun connect(context: Context) {
        val serverURI = "tcp://q93ee3d3.cn.emqx.cloud:11264"
        mqttClient = MqttAndroidClient(context, serverURI, "kotlin_client")
        mqttClient.setCallback(object : MqttCallback {
            override fun messageArrived(topic: String?, message: MqttMessage?) {
                Log.d(TAG, "Receive message: ${message.toString()} from topic: $topic")
                val extra = message.toString()
                val json = JSONObject(extra)
                val msg = json.getString("msg")
                Log.d("msg", msg)
            }

            override fun connectionLost(cause: Throwable?) {
                Log.d(TAG, "Connection lost ${cause.toString()}")
            }

            override fun deliveryComplete(token: IMqttDeliveryToken?) {

            }
        })
        val options = MqttConnectOptions()
        options.setAutomaticReconnect(true)
        // 清除缓存
        options.setCleanSession(true)
        // 设置超时时间，单位：秒
        options.setConnectionTimeout(60)
        // 心跳包发送间隔，单位：秒
        options.setKeepAliveInterval(5)
        // 用户名
        options.setUserName(userName)
        // 密码
        options.setPassword(passWord.toCharArray())
        try {
            mqttClient.connect(options, null, object : IMqttActionListener {
                override fun onSuccess(asyncActionToken: IMqttToken?) {
                    Log.d(TAG, "Connection success")
                    //连接成功发送过来的通知，连接成功才能去订阅消息。
                    //如果需要一次订阅多个主题，需要用for循环去订阅多个
                    subscribe("a/b",0)
                }

                override fun onFailure(asyncActionToken: IMqttToken?, exception: Throwable?) {
                    Log.d(TAG, "Connection failure")
                }
            })
        } catch (e: MqttException) {
            e.printStackTrace()
        }

        myReceiver = MyReceiver()
        val filter = IntentFilter()
        filter.addAction(ConnectivityManager.CONNECTIVITY_ACTION)
        registerReceiver(myReceiver,filter)
    }

    /*
    * 创建 MQTT 订阅
    * 订阅 topic
    * */
    fun subscribe(topic: String, qos: Int = 1) {
        try {
            mqttClient.subscribe(topic, qos, null, object : IMqttActionListener {
                override fun onSuccess(asyncActionToken: IMqttToken?) {
                    Log.d(TAG, "Subscribed to $topic")
                }

                override fun onFailure(asyncActionToken: IMqttToken?, exception: Throwable?) {
                    Log.d(TAG, "Failed to subscribe $topic")
                }
            })
        } catch (e: MqttException) {
            e.printStackTrace()
        }
    }

    /*
    * 取消订阅
    * 取消订阅 topic
    * */
    fun unsubscribe(topic: String) {
        try {
            mqttClient.unsubscribe(topic, null, object : IMqttActionListener {
                override fun onSuccess(asyncActionToken: IMqttToken?) {
                    Log.d(TAG, "Unsubscribed to $topic")
                }

                override fun onFailure(asyncActionToken: IMqttToken?, exception: Throwable?) {
                    Log.d(TAG, "Failed to unsubscribe $topic")
                }
            })
        } catch (e: MqttException) {
            e.printStackTrace()
        }
    }

    /*
    * 发布消息
    * */
    fun publish(topic: String, msg: String, qos: Int = 1, retained: Boolean = false) {
        try {
            val message = MqttMessage()
            message.payload = msg.toByteArray()
            message.qos = qos
            message.isRetained = retained
            mqttClient.publish(topic, message, null, object : IMqttActionListener {
                override fun onSuccess(asyncActionToken: IMqttToken?) {
                    Log.d(TAG, "$msg published to $topic")
                }

                override fun onFailure(asyncActionToken: IMqttToken?, exception: Throwable?) {
                    Log.d(TAG, "Failed to publish $msg to $topic")
                }
            })
        } catch (e: MqttException) {
            e.printStackTrace()
        }
    }

    /*
    * 断开 MQTT 连接
    * */
    fun disconnect() {
        try {
            mqttClient.disconnect(null, object : IMqttActionListener {
                override fun onSuccess(asyncActionToken: IMqttToken?) {
                    Log.d(TAG, "Disconnected")
                }

                override fun onFailure(asyncActionToken: IMqttToken?, exception: Throwable?) {
                    Log.d(TAG, "Failed to disconnect")
                }
            })
        } catch (e: MqttException) {
            e.printStackTrace()
        }
    }




}